#pragma once
#include<iostream>
#include"STLriterator.hpp"
using namespace std;
namespace hcc
{
    //链表的节点
    template<class T>
    struct listnode
    {
        listnode(const T& x = 0)
            :val(x)
            ,next(nullptr)
            ,prev(nullptr)
        {}
        T val;
        listnode* next;
        listnode* prev;
    };
    //迭代器
    template<class T , class ref ,class ptr>
    struct list_iterator
    {
        typedef listnode<T> node;
        typedef list_iterator<T , ref , ptr> iterator;
        node* cur;
        list_iterator(node* x)
            :cur(x)
        {}
        iterator& operator++()
        {
            cur=cur->next;
            return *this;
        }
        iterator operator++(int)
        {
            iterator tem(*this);
            ++(*this);
            return tem;
        }
        iterator& operator--()
        {
            cur=cur->prev;
            return *this;
        }
        iterator operator--(int)
        {
            iterator tem(*this);
            --(*this);
            return tem;
        }
        ref operator*()const  
        {
            return cur->val; 
        }
        ptr operator->()const
        {
            return &(cur->val);
        }
        bool operator!=(const iterator& t)const
        {
            return cur!=t.cur;
        }
    };
    //链表
    template<class T>
    class list
    {
        public:
            typedef listnode<T> node;
            typedef list_iterator<T , T& , T*> iterator;
            typedef list_riterator<iterator , T& , T*> riterator;
            list()
                :_head(new node)
            {
                _head->next=_head;
                _head->prev=_head;
            }
            void push(const T& x)
            {
                node* cur=new node(x);
                node* tail=_head->prev;
                tail->next=cur;
                cur->prev=tail;
                _head->prev=cur;
                cur->next=_head;
            }
            iterator begin()
            {
                return iterator(_head->next);
            }
            iterator end()
            {
                return iterator(_head);
            }
            riterator rbegin()
            {
                return riterator(end());
            }
            riterator rend()
            {
                return riterator(begin());
            }

        private:
            node* _head;
    };

}
